/** @类 渲染者 */
export class Renderer {
  constructor({ el, observer }) {
    this.el = el;
    this.state = true;
    this.observer = observer;
    this.initBuffer();
    this.initCanvas();
    this.initSize();
    this.initDraw();
  }

  /** @辅助 初始化尺寸 */
  initSize() {
    this.onResize();
    window.addEventListener('resize', this.onResize.bind(this));
  }

  /** @辅助 初始化画板 */
  initCanvas() {
    const canvas = document.createElement('canvas');
    canvas.style.backgroundColor = 'gray';
    canvas.style.width = '100%';
    canvas.style.height = '100%';
    this.canvas = canvas;
    this.canvasCtx = canvas.getContext('2d');
    this.el.firstChild && this.el.removeChild(this.el.firstChild);
    this.el.appendChild(canvas);
  }

  /** @辅助 初始化缓存 */
  initBuffer() {
    this.buffer = document.createElement('canvas');
    this.bufferCtx = this.buffer.getContext('2d');
  }

  /** @辅助 初始化渲染 */
  initDraw() {
    if (typeof requestAnimationFrame === 'function') {
			const requestDraw = () => {
				this.observer.dispatch('draw');
        this.state && requestAnimationFrame(requestDraw);
			};
			requestDraw();
		} else {
			const requestDraw = () => {
				this.observer.dispatch('draw');
        this.state && setTimeout(requestDraw, 1000 / 60); // 60fps;
			};
			requestDraw();
		}
  }

  /** @事件 窗口变化 */
  onResize() {
    const {
      top, left, width, height
    } = this.el.getBoundingClientRect();
    this.top = top;
    this.left = left;
    this.width = width;
    this.height = height;
    this.canvas.width = width;
    this.canvas.height = height;
    this.buffer.width = width;
    this.buffer.height = height;
    this.observer.dispatch('resize', this);
  }

  /** @方法 销毁内容 */
  destroy() {
    this.state = false;
    window.removeEventListener('resize', this.onResize.bind(this));
  }
}

export default Renderer;
